package environment.dungeons;

import static org.junit.Assert.*;
import org.junit.*;

import java.math.BigDecimal;
import java.util.HashMap;
import java.util.Map;

import temperature.Temperature;

import environment.Direction;
import environment.borders.Border;
import environment.borders.Door;
import environment.borders.Void;
import environment.borders.Wall;

/**
 * Een testklasse voor de klasse Square.
 * Deze bevat alle testmethoden om setters en speciale mutators
 * te controleren van de klasse 'transparant vakje'.
 * 
 * @author 	Nathan Bekaert & Philippe de Potter de ten Broeck
 * @version 1.0
 */
public class TransparentSquareTest {
	
	Square transparant1;
	Square transparant2;
	Square transparant3;
	
	@BeforeClass
	public static void setUpBeforeClass() throws Exception {
	}

	@AfterClass
	public static void tearDownAfterClass() throws Exception {
	}

	@Before
	public void setUp() throws Exception {
		transparant1 = new TransparentSquare(Direction.EAST);
		transparant2 = new TransparentSquare(Temperature.CELSIUS_1, BigDecimal.TEN, Direction.CEILING, true);
		transparant3 = new TransparentSquare(Temperature.CELSIUS_0, new BigDecimal(50.00), Direction.NORTH, false);
	}

	@After
	public void tearDown() throws Exception {
	}
	
	//CONSTRUCTION OF TRANSPARENTSQUARES
	
	@Test
	public void constructor() {
		assertTrue(transparant1.getTemperature().equals(Temperature.CELSIUS_0));
		assertTrue(transparant1.getHumidity().equals(BigDecimal.TEN));
		assertTrue(transparant2.getTemperature().equals(Temperature.CELSIUS_1));
		assertTrue(transparant2.getHumidity().equals(BigDecimal.TEN));
		assertTrue(transparant3.getTemperature().equals(Temperature.CELSIUS_0));
		assertTrue(transparant3.getHumidity().equals(new BigDecimal(50.00)));
		for(Direction direction: Direction.values()) {
			if(! (transparant1.getBorderAt(direction) instanceof Door) &&
					(direction == Direction.EAST))
				assert false;
			if(! (transparant2.getBorderAt(direction) instanceof Door) &&
					(direction == Direction.CEILING))
				assert false;
			if(! (transparant2.getBorderAt(direction) instanceof Door) &&
					(direction == Direction.FLOOR))
				assert false;
			if(! (transparant3.getBorderAt(direction) instanceof Door) &&
					(direction == Direction.NORTH))
				assert false;
			if(! (transparant1.getBorderAt(direction) instanceof Void) &&
					(direction != Direction.EAST))
				assert false;
			if(! (transparant2.getBorderAt(direction) instanceof Void) &&
					(direction != Direction.CEILING) && (direction != Direction.FLOOR))
				assert false;
			if(! (transparant3.getBorderAt(direction) instanceof Void) &&
					(direction != Direction.NORTH))
				assert false;
		}
	}
	
	//BORDERS

	@Test
	public void canHaveAsBorders_Wall() {
		Map<Direction, Border> newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.WEST, new Wall(false));
		assertTrue(! transparant1.canHaveAsBorders(newBorders));
		newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.EAST, new Wall(false));
		assertTrue(! transparant1.canHaveAsBorders(newBorders));
		newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.NORTH, new Wall(false));
		assertTrue(! transparant1.canHaveAsBorders(newBorders));
	}
	
	@Test
	public void canHaveAsBorders_DoorInRightDirections() {
		Map<Direction, Border> newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.WEST, new Door(false));
		assertTrue(transparant1.canHaveAsBorders(newBorders));
		newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.EAST, new Door(true));
		assertTrue(transparant1.canHaveAsBorders(newBorders));
		newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.EAST, new Door(false));
		newBorders.put(Direction.WEST, new Door(true));
		assertTrue(transparant1.canHaveAsBorders(newBorders));
	}
	
	@Test
	public void canHaveAsBorders_DoorInWrongDirections() {
		Map<Direction, Border> newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.NORTH, new Door(false));
		assertTrue(! transparant2.canHaveAsBorders(newBorders));
		newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.CEILING, new Door(false));
		assertTrue(! transparant3.canHaveAsBorders(newBorders));
	}
	
	@Test
	public void canHaveAsBorders_Void() {
		Map<Direction, Border> newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.SOUTH, new Void());
		assertTrue(transparant3.canHaveAsBorders(newBorders));
		newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.CEILING, new Void());
		assertTrue(transparant2.canHaveAsBorders(newBorders));
		newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.CEILING, new Void());
		newBorders.put(Direction.FLOOR, new Void());
		assertTrue(! transparant2.canHaveAsBorders(newBorders));
		newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.NORTH, new Void());
		assertTrue(! transparant3.canHaveAsBorders(newBorders));
		newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.SOUTH, new Void());
		assertTrue(transparant1.canHaveAsBorders(newBorders));
	}
	
	@Test
	public void canHaveAsBorders_Terminated() {
		Map<Direction, Border> newBorders = new HashMap<Direction, Border>();
		newBorders.put(Direction.WEST, new Door(false));
		transparant1.terminate();
		assertTrue(! transparant1.canHaveAsBorders(newBorders));
	}
}
